 package com.nbcio.iot.service.impl;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.lang.tree.Tree;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.nbcio.common.core.utils.MapstructUtils;
import com.nbcio.common.core.utils.StringUtils;
import com.nbcio.common.core.utils.TreeBuildUtils;
import com.nbcio.iot.domain.entity.IotDeviceGroup;
import com.nbcio.iot.domain.bo.IotDeviceGroupBo;
import com.nbcio.iot.domain.vo.IotDeviceGroupVo;
import com.nbcio.iot.mapper.IotDeviceGroupMapper;
import com.nbcio.iot.service.IIotDeviceGroupService;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;

import java.util.Collection;
import java.util.List;
import java.util.ArrayList;

/**
 * 设备分组Service业务层处理
 */
@RequiredArgsConstructor
@Service
public class IotDeviceGroupServiceImpl implements IIotDeviceGroupService {

    private final IotDeviceGroupMapper baseMapper;

    @Override
    public IotDeviceGroupVo queryById(Long groupId) {
        return baseMapper.selectVoById(groupId);
    }

    @Override
    public List<IotDeviceGroupVo> queryList(IotDeviceGroupBo bo) {
        IotDeviceGroup build = MapstructUtils.convert(bo, IotDeviceGroup.class);
        if (build == null) {
            build = new IotDeviceGroup();
        }
        return baseMapper.selectDeviceGroupVoList(build);
    }

    @Override
    public List<IotDeviceGroupVo> queryTreeList() {
        List<IotDeviceGroupVo> list = baseMapper.selectDeviceGroupTreeList();
        // 使用简单的递归方式构建树结构
        return buildTree(list, 0L);
    }

    /**
     * 递归构建树结构
     */
    private List<IotDeviceGroupVo> buildTree(List<IotDeviceGroupVo> list, Long parentId) {
        List<IotDeviceGroupVo> result = new ArrayList<>();
        for (IotDeviceGroupVo item : list) {
            if (parentId.equals(item.getParentId())) {
                List<IotDeviceGroupVo> children = buildTree(list, item.getGroupId());
                if (!children.isEmpty()) {
                    item.setChildren(children);
                }
                result.add(item);
            }
        }
        return result;
    }

    @Override
    public Boolean insertByBo(IotDeviceGroupBo bo) {
        IotDeviceGroup add = MapstructUtils.convert(bo, IotDeviceGroup.class);
        validEntityBeforeSave(add);
        boolean flag = baseMapper.insert(add) > 0;
        if (flag) {
            bo.setGroupId(add.getGroupId());
        }
        return flag;
    }

    @Override
    public Boolean updateByBo(IotDeviceGroupBo bo) {
        IotDeviceGroup update = MapstructUtils.convert(bo, IotDeviceGroup.class);
        validEntityBeforeSave(update);
        return baseMapper.updateById(update) > 0;
    }

    @Override
    public Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid) {
        if (isValid) {
            // 检查是否有子分组
            for (Long id : ids) {
                IotDeviceGroup group = baseMapper.selectById(id);
                if (group != null) {
                    LambdaQueryWrapper<IotDeviceGroup> qw = new LambdaQueryWrapper<>();
                    qw.eq(IotDeviceGroup::getParentId, id);
                    List<IotDeviceGroupVo> children = baseMapper.selectVoList(qw);
                    if (!children.isEmpty()) {
                        throw new RuntimeException("分组【" + group.getGroupName() + "】下还有子分组，无法删除");
                    }
                }
            }
        }
        return baseMapper.deleteBatchIds(ids) > 0;
    }

    @Override
    public Boolean checkGroupNameUnique(IotDeviceGroupBo bo) {
        Long groupId = StringUtils.isNull(bo.getGroupId()) ? -1L : bo.getGroupId();
        LambdaQueryWrapper<IotDeviceGroup> qw = new LambdaQueryWrapper<>();
        qw.eq(IotDeviceGroup::getGroupName, bo.getGroupName());
        IotDeviceGroup info = baseMapper.selectOne(qw);
        if (StringUtils.isNotNull(info) && info.getGroupId().longValue() != groupId.longValue()) {
            return false;
        }
        return true;
    }

    /**
     * 保存前的数据校验
     */
    private void validEntityBeforeSave(IotDeviceGroup entity) {
        // 做一些数据校验,如唯一约束
    }
}